#include<iostream>
#include<cstring>
#include<sys/socket.h>
#include<netinet/in.h>
#include<unistd.h>
#include<arpa/inet.h>
#include<sys/types.h>
#include<cstdlib>
const static int defaultsockfd = -1;
class TcpServer 
{
private:
    uint16_t _port;
    int _sockfd; //?
public:
    TcpServer(uint16_t port) : _port(port), _sockfd(defaultsockfd) {}
    ~TcpServer() 
    {
        if (_sockfd != defaultsockfd) 
        {
            close(_sockfd);
        }
    }
    void InitServer() 
    {
        // Initialize server socket
        _sockfd = socket(AF_INET, SOCK_STREAM, 0);
        if (_sockfd < 0) 
        {
            std::cerr << "Error creating socket" << std::endl;
            exit(EXIT_FAILURE);
        }
        std::cout<<"Socket created successfully" << std::endl;

        // Set up server address
        struct sockaddr_in local;
        memset(&local, 0, sizeof(local));
        local.sin_family = AF_INET;
        local.sin_addr.s_addr = INADDR_ANY;
        local.sin_port = htons(_port);

        // Bind the socket to the address
        if (bind(_sockfd, (struct sockaddr*)&local, sizeof(local)) < 0) 
        {
            std::cerr << "Error binding socket" << std::endl;
            close(_sockfd);
            exit(EXIT_FAILURE);
        }

        // Start listening for incoming connections
        if (listen(_sockfd, 5) < 0) 
        {
            std::cerr << "Error listening on socket" << std::endl;
            close(_sockfd);
            exit(EXIT_FAILURE);
        }
    }
    void Loop() 
    {
        while (true) 
        {
            // Accept incoming connection
            struct sockaddr_in client_addr;
            socklen_t client_len = sizeof(client_addr);
            int client_sockfd = accept(_sockfd, (struct sockaddr*)&client_addr, &client_len);
            if (client_sockfd < 0) 
            {
                std::cerr << "Error accepting connection" << std::endl;
                continue;
            }

            // Handle the connection
            char buffer[1024];
            ssize_t bytes_received = recv(client_sockfd, buffer, sizeof(buffer), 0);
            if (bytes_received > 0) 
            {
                send(client_sockfd, buffer, bytes_received, 0);
            }

            close(client_sockfd);
        }
    }

};